import React, { useState, useRef } from 'react';
import { Button, Card, Badge, UploadIcon, CheckIcon, CloseIcon } from "@repo/ui";
import styles from './CustomFlashPage.module.css';

interface FlashFile {
  name: string;
  size: number;
  type: string;
  address?: string;
  file?: File;
}

interface FlashStep {
  id: string;
  title: string;
  description: string;
  status: 'pending' | 'running' | 'completed' | 'error';
  progress?: number;
}

const CustomFlashPage: React.FC = () => {
  const [selectedFiles, setSelectedFiles] = useState<FlashFile[]>([]);
  const [isFlashing, setIsFlashing] = useState(false);
  const [flashSteps, setFlashSteps] = useState<FlashStep[]>([]);
  const [selectedBoard, setSelectedBoard] = useState('esp32');
  const fileInputRef = useRef<HTMLInputElement>(null);

  const boardTypes = [
    { id: 'esp32', name: 'ESP32', description: '标准ESP32开发板' },
    { id: 'esp32s2', name: 'ESP32-S2', description: 'ESP32-S2系列' },
    { id: 'esp32s3', name: 'ESP32-S3', description: 'ESP32-S3系列' },
    { id: 'esp32c3', name: 'ESP32-C3', description: 'ESP32-C3系列' }
  ];

  const handleFileSelect = (event: React.ChangeEvent<HTMLInputElement>) => {
    const files = Array.from(event.target.files || []);
    
    const newFiles: FlashFile[] = files.map(file => ({
      name: file.name,
      size: file.size,
      type: file.name.split('.').pop() || '',
      file,
      address: getDefaultAddress(file.name)
    }));

    setSelectedFiles(prev => [...prev, ...newFiles]);
  };

  const getDefaultAddress = (filename: string): string => {
    if (filename.includes('bootloader')) return '0x1000';
    if (filename.includes('partition')) return '0x8000';
    if (filename.includes('app') || filename.includes('firmware')) return '0x10000';
    return '0x10000';
  };

  const removeFile = (index: number) => {
    setSelectedFiles(prev => prev.filter((_, i) => i !== index));
  };

  const updateFileAddress = (index: number, address: string) => {
    setSelectedFiles(prev => 
      prev.map((file, i) => 
        i === index ? { ...file, address } : file
      )
    );
  };

  const formatFileSize = (bytes: number): string => {
    if (bytes === 0) return '0 B';
    const k = 1024;
    const sizes = ['B', 'KB', 'MB', 'GB'];
    const i = Math.floor(Math.log(bytes) / Math.log(k));
    return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i];
  };

  const startFlashing = async () => {
    if (selectedFiles.length === 0) return;

    setIsFlashing(true);
    
    const steps: FlashStep[] = [
      { id: '1', title: '连接设备', description: '正在连接ESP32设备...', status: 'running' },
      { id: '2', title: '擦除Flash', description: '清空目标地址空间...', status: 'pending' },
      { id: '3', title: '写入固件', description: '将固件写入设备...', status: 'pending' },
      { id: '4', title: '验证固件', description: '验证写入的固件...', status: 'pending' },
      { id: '5', title: '重启设备', description: '重启设备并启动新固件...', status: 'pending' }
    ];

    setFlashSteps(steps);

    // 模拟刷机过程
    for (let i = 0; i < steps.length; i++) {
      await new Promise(resolve => setTimeout(resolve, 2000));
      
      setFlashSteps(prev => 
        prev.map((step, index) => {
          if (index === i) {
            return { ...step, status: 'completed', progress: 100 };
          } else if (index === i + 1) {
            return { ...step, status: 'running', progress: 0 };
          }
          return step;
        })
      );

      // 模拟写入固件的进度
      if (i === 2) {
        for (let progress = 0; progress <= 100; progress += 10) {
          await new Promise(resolve => setTimeout(resolve, 200));
          setFlashSteps(prev => 
            prev.map((step, index) => 
              index === i ? { ...step, progress } : step
            )
          );
        }
      }
    }

    setIsFlashing(false);
  };

  const resetFlashing = () => {
    setFlashSteps([]);
    setIsFlashing(false);
  };

  const getStepIcon = (status: FlashStep['status']) => {
    switch (status) {
      case 'completed':
        return <CheckIcon className={styles.stepIcon} size={20} />;
      case 'running':
        return (
          <div className={styles.spinner}>
            <svg className={styles.stepIcon} fill="none" viewBox="0 0 24 24">
              <circle className={styles.spinnerCircle} cx="12" cy="12" r="10" stroke="currentColor" strokeWidth="4"/>
              <path className={styles.spinnerPath} fill="currentColor" d="m4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4zm2 5.291A7.962 7.962 0 014 12H0c0 3.042 1.135 5.824 3 7.938l3-2.647z"/>
            </svg>
          </div>
        );
      case 'error':
        return <CloseIcon className={styles.stepIcon} size={20} />;
      default:
        return (
          <div className={styles.stepIcon}>
            <div className={styles.stepNumber}>{parseInt(status)}</div>
          </div>
        );
    }
  };

  return (
    <div className={styles.container}>
      <div className={styles.header}>
        <h1>自定义固件刷写</h1>
        <p>上传并刷写自定义固件到ESP32设备</p>
      </div>

      <div className={styles.content}>
        <div className={styles.leftPanel}>
          {/* 开发板选择 */}
          <Card className={styles.section}>
            <h3>选择开发板类型</h3>
            <div className={styles.boardGrid}>
              {boardTypes.map(board => (
                <button
                  key={board.id}
                  className={`${styles.boardCard} ${selectedBoard === board.id ? styles.selected : ''}`}
                  onClick={() => setSelectedBoard(board.id)}
                >
                  <div className={styles.boardName}>{board.name}</div>
                  <div className={styles.boardDesc}>{board.description}</div>
                </button>
              ))}
            </div>
          </Card>

          {/* 文件选择 */}
          <Card className={styles.section}>
            <div className={styles.sectionHeader}>
              <h3>固件文件</h3>
              <Button
                onClick={() => fileInputRef.current?.click()}
                variant="outline"
                size="sm"
              >
                添加文件
              </Button>
            </div>
            
            <input
              ref={fileInputRef}
              type="file"
              multiple
              accept=".bin,.hex,.elf"
              onChange={handleFileSelect}
              className={styles.hiddenInput}
            />

            {selectedFiles.length === 0 ? (
              <div className={styles.emptyState}>
                <UploadIcon className={styles.emptyIcon} size={24} />
                <p>点击"添加文件"选择固件文件</p>
                <p className={styles.supportedFormats}>支持 .bin, .hex, .elf 格式</p>
              </div>
            ) : (
              <div className={styles.fileList}>
                {selectedFiles.map((file, index) => (
                  <div key={index} className={styles.fileItem}>
                    <div className={styles.fileInfo}>
                      <div className={styles.fileName}>{file.name}</div>
                      <div className={styles.fileDetails}>
                        <Badge variant="default" size="sm">{file.type.toUpperCase()}</Badge>
                        <span>{formatFileSize(file.size)}</span>
                      </div>
                    </div>
                    <div className={styles.fileAddress}>
                      <label>地址:</label>
                      <input
                        type="text"
                        value={file.address}
                        onChange={(e) => updateFileAddress(index, e.target.value)}
                        className={styles.addressInput}
                        placeholder="0x10000"
                      />
                    </div>
                    <Button
                      onClick={() => removeFile(index)}
                      variant="ghost"
                      size="sm"
                      className={styles.removeButton}
                    >
                      ×
                    </Button>
                  </div>
                ))}
              </div>
            )}
          </Card>

          {/* 刷写控制 */}
          <Card className={styles.section}>
            <div className={styles.flashControls}>
              <Button
                onClick={startFlashing}
                disabled={selectedFiles.length === 0 || isFlashing}
                className={styles.flashButton}
              >
                {isFlashing ? '刷写中...' : '开始刷写'}
              </Button>
              {flashSteps.length > 0 && (
                <Button
                  onClick={resetFlashing}
                  variant="outline"
                  disabled={isFlashing}
                >
                  重置
                </Button>
              )}
            </div>
          </Card>
        </div>

        <div className={styles.rightPanel}>
          {/* 刷写进度 */}
          {flashSteps.length > 0 && (
            <Card className={styles.section}>
              <h3>刷写进度</h3>
              <div className={styles.stepsList}>
                {flashSteps.map((step) => (
                  <div 
                    key={step.id} 
                    className={`${styles.step} ${styles[step.status]}`}
                  >
                    <div className={styles.stepIndicator}>
                      {getStepIcon(step.status)}
                    </div>
                    <div className={styles.stepContent}>
                      <div className={styles.stepTitle}>{step.title}</div>
                      <div className={styles.stepDescription}>{step.description}</div>
                      {step.status === 'running' && step.progress !== undefined && (
                        <div className={styles.progressBar}>
                          <div 
                            className={styles.progressFill}
                            style={{ width: `${step.progress}%` }}
                          />
                        </div>
                      )}
                    </div>
                  </div>
                ))}
              </div>
            </Card>
          )}

          {/* 使用说明 */}
          <Card className={styles.section}>
            <h3>使用说明</h3>
            <div className={styles.instructions}>
              <div className={styles.instruction}>
                <span className={styles.stepNum}>1</span>
                <span>选择对应的ESP32开发板类型</span>
              </div>
              <div className={styles.instruction}>
                <span className={styles.stepNum}>2</span>
                <span>上传固件文件(.bin, .hex, .elf)</span>
              </div>
              <div className={styles.instruction}>
                <span className={styles.stepNum}>3</span>
                <span>设置正确的Flash地址</span>
              </div>
              <div className={styles.instruction}>
                <span className={styles.stepNum}>4</span>
                <span>确保设备已连接并点击开始刷写</span>
              </div>
            </div>
            
            <div className={styles.tips}>
              <h4>常用地址:</h4>
              <ul>
                <li><code>0x1000</code> - Bootloader</li>
                <li><code>0x8000</code> - Partition Table</li>
                <li><code>0x10000</code> - Application</li>
              </ul>
            </div>
          </Card>
        </div>
      </div>
    </div>
  );
};

export default CustomFlashPage;
